package com.xxxx.server;

import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.poi.util.Units;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.usermodel.XWPFParagraph;
import org.apache.poi.xwpf.usermodel.XWPFRun;
import org.apache.poi.xwpf.usermodel.XWPFTable;
import org.apache.poi.xwpf.usermodel.XWPFTableCell;
import org.apache.poi.xwpf.usermodel.XWPFTableRow;
import org.junit.Test;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author Honors
 * @date 2021/9/20
 */
public class T4 {

    @Test
    public void t1() {
        // 图片1
        Map<String, Object> imgMap1 = new HashMap<>();
        imgMap1.put("imgPath", "D:\\test\\img\\tu2.jpg");
        // 图片宽度
        imgMap1.put("imgWidth", 100);
        // 图片高度
        imgMap1.put("imgHeight", 100);

        // 图片2
        Map<String, Object> imgMap2 = new HashMap<>();
        imgMap2.put("imgPath", "D:\\test\\img\\tu1.jpeg");
        // 图片宽度
        imgMap2.put("imgWidth", 100);
        // 图片高度
        imgMap2.put("imgHeight", 100);

        // 模板文件地址
        String templatePath = "D:\\test\\职业技能等级认定成绩汇总表.docx";
        // 模板文件地址
        String outFile = "D:\\test\\测试文件.docx";

        // 替换数据
        Map<String, Object> map = new HashMap<>();
        // 模板文件地址
        map.put("templateFile", templatePath);
        // 替换文件地址
        map.put("outFile", outFile);
        // 处罚单编号
        map.put("$编号$", "00001");
        // 被处罚人
        map.put("$用户$", "填表人：" + "张三"
                + " " + " " + " "
                + "日期："
                + new SimpleDateFormat("yyyy年MM月dd日").format(new Date()));
        // 用户组
        map.put("$单位$", "开发测试用户组");
        // 培训项目
        map.put("$项目$", "趣味运动会");
        // 处罚描述
        map.put("$处罚原因$", "XXX" + "项目" + "XXX" + "课程" +
                "教员" + "XXX" + "于__月__日" +
                "由于_________________,根据《培训中心教员授课管理规范指导手册》条例给予_______处罚。");
        // 工程师签字
        map.put("$签字$", "00001");
        // 图1
        map.put("#图片1#", imgMap1);
        // 图2
        map.put("#图片2#", imgMap2);

        // 模板替换
        replacePlaceholderDocument(map);
    }

    public static void replacePlaceholderDocument(Map<String, Object> map) {
        File imgFile = null;
        XWPFDocument document = null;
        FileOutputStream outputStream = null;
        FileInputStream fis = null;
        try {
            // 读取文件
            fis = new FileInputStream((String) map.get("templateFile"));
            document = new XWPFDocument(fis);
            // 获取文件表格
            List<XWPFTable> tables = document.getTables();
            for (XWPFTable table : tables) {
                // 获取表格的所有行
                List<XWPFTableRow> rows = table.getRows();
                for (XWPFTableRow row : rows) {
                    // 获取表格的所有列
                    List<XWPFTableCell> tableCells = row.getTableCells();
                    for (XWPFTableCell cell : tableCells) {
                        // 获取单元格的文本内容
                        String text = cell.getText();
                        // 匹配占位符，赋值
                        for (String key : map.keySet()) {
                            // 判断该列中是否存在占位符
                            if (text.contains(key)) {
                                if (key.contains("$")) {// $ 文本标识符
                                    // 删除占位符
                                    cell.removeParagraph(0);
                                    // 替换
                                    cell.setText((String) map.get(key));
                                }
                                if (key.contains("#")) {// # 图片标识符
                                    Map imgMap = (HashMap) map.get(key);
                                    // 图片路径
                                    String imgPath = (String) imgMap.get("imgPath");
                                    // 图片宽度
                                    Integer imgWidth = (Integer) imgMap.get("imgWidth");
                                    // 图片高度
                                    Integer imgHeight = (Integer) imgMap.get("imgHeight");
                                    // 删除占位符
                                    cell.removeParagraph(0);
                                    // 添加段落
                                    XWPFParagraph xwpfParagraph = cell.addParagraph();
                                    XWPFRun xwpfPicture = xwpfParagraph.createRun();
                                    // 截取图片后缀，判断图片类型
                                    String substring = imgPath.substring(imgPath.lastIndexOf(".") + 0);
                                    int pictureTypePng = 0;
                                    if (substring.equals(".jpeg")
                                            || substring.equals(".JPEG")
                                            || substring.equals(".jpg")
                                            || substring.equals(".JPG")) {
                                        pictureTypePng = XWPFDocument.PICTURE_TYPE_JPEG;
                                    } else {
                                        pictureTypePng = XWPFDocument.PICTURE_TYPE_PNG;
                                    }
                                    try {
                                        // 找到图片文件
                                        imgFile = new File(imgPath);
                                        // 读取图片
                                        fis = new FileInputStream(imgFile);
                                        // fis 文件地址，pictureTypePng 图片类型，filename 图片名称
                                        xwpfPicture.addPicture(fis, pictureTypePng, "picture",
                                                Units.toEMU(imgWidth), Units.toEMU(imgHeight));
                                    } catch (InvalidFormatException e) {
                                        e.printStackTrace();
                                    } catch (IOException e) {
                                        e.printStackTrace();
                                    }
                                }
                            }
                        }
                    }
                }
            }
            outputStream = new FileOutputStream((String) map.get("outFile"));
            document.write(outputStream);
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                document.close();
                outputStream.close();
                fis.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

}
